package com.ylsk.check.service.impl;

import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import com.alibaba.fastjson2.JSON;
import com.ylsk.check.domain.*;
import com.ylsk.check.domain.dto.CheckRecordDTO;
import com.ylsk.check.domain.emum.BasicInfoTemplateEnum;
import com.ylsk.check.domain.emum.ConstructionStatusEnum;
import com.ylsk.check.domain.so.CheckRecordSO;
import com.ylsk.check.domain.vo.CheckRecordVO;
import com.ylsk.check.domain.vo.CheckRecordDetailVO;
import com.ylsk.check.domain.vo.ReportInfoVO;
import com.ylsk.check.domain.vo.TodayCheckTaskVO;
import com.ylsk.check.mapper.CheckTaskMapper;
import com.ylsk.check.mapper.WithdrawalReportMapper;
import com.ylsk.check.service.ICheckItemRecordService;
import com.ylsk.check.service.ICheckProblemService;
import com.ylsk.common.annotation.DataScope;
import com.ylsk.common.config.SnowIdConfig;
import com.ylsk.common.exception.ServiceException;
import com.ylsk.common.utils.SecurityUtils;
import com.ylsk.common.utils.StringUtils;
import com.ylsk.system.domain.FileInfo;
import com.ylsk.system.domain.FileSimple;
import com.ylsk.system.helper.FileHelper;
import com.ylsk.system.service.IMinioFileService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.ylsk.check.mapper.CheckRecordMapper;
import com.ylsk.check.service.ICheckRecordService;
import org.springframework.transaction.annotation.Transactional;

/**
 * 施工检查记录Service业务层处理
 *
 * @author yangsy
 * @date 2023-12-18
 */
@Service
public class CheckRecordServiceImpl implements ICheckRecordService
{
    @Autowired
    private CheckRecordMapper checkRecordMapper;

    @Autowired
    private SnowIdConfig snowIdConfig;

    @Autowired
    private ICheckItemRecordService checkItemRecordService;

    @Autowired
    private FileHelper fileHelper;

    @Autowired
    private IMinioFileService minioFileService;

    @Autowired
    private ICheckProblemService checkProblemService;

    @Autowired
    private ReportInfoHelper helper;

    @Autowired
    private CheckTaskMapper checkTaskMapper;

    @Autowired
    private WithdrawalReportMapper withdrawalReportMapper;

    /**
     * 查询施工检查记录
     *
     * @param checkRecordId 施工检查记录主键
     * @return 施工检查记录
     */
    @Override
    public CheckRecordVO selectCheckRecordByCheckRecordId(Long checkRecordId)
    {
        CheckRecordVO checkRecordVO = checkRecordMapper.selectCheckRecordByCheckRecordId(checkRecordId);
        //构建附件信息
        Long problemFileId = checkRecordVO.getProblemFileId();
        if(null != problemFileId){
            List<FileSimple> fileSimpleList = minioFileService.getFileListByBusinessId(problemFileId);
            checkRecordVO.setProblemFile(fileSimpleList);
        }

        //构建检查项记录
        CheckItemRecord checkItemRecord = new CheckItemRecord();
        checkItemRecord.setCheckRecordId(checkRecordId);
        List<CheckItemRecord> checkItemRecordList = checkItemRecordService.selectCheckItemRecordList(checkItemRecord);
        checkRecordVO.setCheckItemRecordList(checkItemRecordList);
        return checkRecordVO;
    }

    /**
     * 查询施工检查记录列表
     *
     * @param checkRecordSO 施工检查记录
     * @return 施工检查记录
     */
    @Override
    @DataScope(deptAlias = "sd",userAlias = "su")
    public List<CheckRecordVO> selectCheckRecordList(CheckRecordSO checkRecordSO)
    {
        return checkRecordMapper.selectCheckRecordList(checkRecordSO);
    }

    /**
     * 新增施工检查记录
     *
     * @param checkRecordDTO 施工检查记录
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int insertCheckRecord(CheckRecordDTO checkRecordDTO)
    {
        //  施工报备id
        final Long reportInfoId = checkRecordDTO.getReportInfoId();
        //  施工检查记录id
        final long checkRecordId = snowIdConfig.getSnowId();
        //  施工检查照片id
        final long problemFileId = snowIdConfig.getSnowId();
        //  施工检查任务id
        final Long checkTaskId = checkRecordDTO.getCheckTaskId();
        //  检查方式  0 线上检查 1 现场检查 2 网络+现场检查
        final Integer checkMethod = checkRecordDTO.getCheckMethod();
        //现场检查照片或者视频
        String problemFile = checkRecordDTO.getProblemFile();
        //检查内容
        String checkItemRecord = checkRecordDTO.getCheckItemRecord();
        if(StringUtils.isEmpty(checkItemRecord)){
            throw new ServiceException("检查内容不能为空");
        }
        if(null == reportInfoId){
            throw new ServiceException("施工报备id不能为空!");
        }
        //  针对现场检查 照片数量做一个限制
        if(checkMethod == 1 ){
            if(StringUtils.isEmpty(problemFile)){
                throw new ServiceException("现场检查照片不能为空,并且现场检查照片不能低于7张");
            }else{
                List<Long> fileIdList = Arrays.asList(problemFile.split(",")).stream().map(s -> Long.parseLong(s.trim())).collect(Collectors.toList());
                List<FileInfo> fileInfoList = fileHelper.getFileByFileId(fileIdList);
                boolean isVideo = false;
                for (FileInfo fileInfo : fileInfoList) {
                    //文件类型
                    String fileSuffix = fileInfo.getFileSuffix();
                    if(fileSuffix.equalsIgnoreCase("mp4") || fileSuffix.equalsIgnoreCase("avi") || fileSuffix.equalsIgnoreCase("mov")){
                        isVideo = true;
                        break;
                    }
                }
                //  如果有视频都不需要数量，如果非视频 那么现场检查照片不能低于5张。
//                if(isVideo == false && fileIdList.size() < 7){
//                    throw new ServiceException("场检查照片不能低于7张,现场照片包括但不限于（①施工标志 ②作业区距离标志 ③限速过度值 ④线性引导标 ⑤减速让行标 ⑥附设警示灯的路栏图 ⑦作业区结束标等)");
//                }
            }
        }

        CheckRecord checkRecord = new CheckRecord();
        BeanUtils.copyProperties(checkRecordDTO,checkRecord);

        List<CheckItemRecord> checkItemRecordList = JSON.parseArray(checkItemRecord, CheckItemRecord.class);
        //是否存在问题  标识
        boolean isProblem = false;
        for (CheckItemRecord itemRecord : checkItemRecordList) {
            itemRecord.setCheckItemRecordId(snowIdConfig.getSnowId());
            itemRecord.setCheckRecordId(checkRecordId);
            //  是否检查 0是 1 否
            itemRecord.setIsCheck(itemRecord.getCheckResult() == null ? 0 : 1 );
            //   检查结果等于1 说明有问题  只要有一项没通过 都不需要再次赋值
            if(itemRecord.getCheckResult() != null && 1 == itemRecord.getCheckResult() && isProblem == false){
                isProblem = true;
            }
        }

        //存储检查项目
        checkItemRecordService.saveBatch(checkItemRecordList);

        //存储现场检查照片或者视频
        if(StringUtils.isNotEmpty(problemFile)){
            fileHelper.saveBusinessFileData(problemFile,problemFileId);
        }
        checkRecord.setCheckRecordId(checkRecordId);
        checkRecord.setProblemFileId(problemFileId);

        //  如果有一项检查未通过 需要写入检查问题表里面去 当成问题处理
        ReportInfo reportInfo = helper.getReportInfo(reportInfoId);
        if(isProblem){
            checkProblemService.insertCheckProblem(checkRecord,reportInfo);
        }

        //  设置检查状态为已检查
        if( null != checkTaskId){
            CheckTask checkTask = checkTaskMapper.selectById(checkTaskId);
            //  如果当前检查单子是撤场上报
            if(checkTask.getTbName().equals(BasicInfoTemplateEnum.INS_WITHDRAWAL_REPORT.getTbName())){
                WithdrawalReport withdrawalReport = withdrawalReportMapper.selectById(checkTask.getReportBusinessId());
                if(withdrawalReport == null && withdrawalReport.getEndProject() == 1){
                   reportInfo.setConstructionStatus(ConstructionStatusEnum.END.getCode());
                   helper.updateReportConstructionStatus(reportInfo,ConstructionStatusEnum.END);
                }
            }
            checkTask.setTaskStatus(1);
            checkTask.setCheckTaskTime(new Date());
            checkTaskMapper.updateById(checkTask);
        }
        //设置施工状态
        checkRecord.setConstructionStatus(reportInfo.getConstructionStatus());
        //设置检查人
        checkRecord.setCheckBy(SecurityUtils.getUserId());
        return checkRecordMapper.insert(checkRecord);
    }

    /**
     * 修改施工检查记录
     *
     * @param checkRecordDTO 施工检查记录
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateCheckRecord(CheckRecordDTO checkRecordDTO)
    {
        final Long checkRecordId = checkRecordDTO.getCheckRecordId();
        if(null == checkRecordId){
            throw new ServiceException("checkRecordId is null");
        }

        CheckRecord checkRecord = new CheckRecord();
        BeanUtils.copyProperties(checkRecordDTO,checkRecord);

        //检查内容
        String checkItemRecord = checkRecordDTO.getCheckItemRecord();
        if(StringUtils.isEmpty(checkItemRecord)){
            throw new ServiceException("检查内容不能为空");
        }

        List<CheckItemRecord> checkItemRecordList = JSON.parseArray(checkItemRecord, CheckItemRecord.class);
        checkItemRecordService.saveOrUpdateBatch(checkItemRecordList);

        //更新附件信息
        String problemFile = checkRecordDTO.getProblemFile();
        CheckRecord _checkRecord = checkRecordMapper.selectById(checkRecordId);
        fileHelper.updateBusinessFileData(problemFile,_checkRecord.getProblemFileId());
        return checkRecordMapper.updateCheckRecord(checkRecord);
    }

    /**
     * 批量删除施工检查记录
     *
     * @param checkRecordIds 需要删除的施工检查记录主键
     * @return 结果
     */
    @Override
    public int deleteCheckRecordByCheckRecordIds(Long[] checkRecordIds)
    {
        return checkRecordMapper.deleteCheckRecordByCheckRecordIds(checkRecordIds);
    }

    /**
     * 删除施工检查记录信息
     *
     * @param checkRecordId 施工检查记录主键
     * @return 结果
     */
    @Override
    public int deleteCheckRecordByCheckRecordId(Long checkRecordId)
    {
        return checkRecordMapper.deleteCheckRecordByCheckRecordId(checkRecordId);
    }

    @Override
    @DataScope(deptAlias = "sd")
    public List<TodayCheckTaskVO> selectTodayCheckTaskList(CheckRecordSO checkRecordSO) {
        return checkRecordMapper.selectTodayCheckTaskList(checkRecordSO);
    }

    @Override
    public CheckRecordDetailVO getCheckRecrdDetailInfo(Long checkRecordId) {
        //施工检查问题记录
        CheckRecordDetailVO checkRecordDetailVO = checkRecordMapper.getCheckRecrdDetailInfo(checkRecordId);

        //检查问题附件
        Long problemFileId = checkRecordDetailVO.getProblemFileId();
        if(null != problemFileId){
            checkRecordDetailVO.setProblemFile(fileHelper.getFileByBusinessId(problemFileId));
        }

        //整改附件
        Long rectificationFileId = checkRecordDetailVO.getRectificationFileId();
        if(null != rectificationFileId){
            checkRecordDetailVO.setRectificationFile(fileHelper.getFileByBusinessId(rectificationFileId));
        }
        //整改复查附件
        Long reviewFileId = checkRecordDetailVO.getReviewFileId();
        if(null != reviewFileId){
            checkRecordDetailVO.setReviewFile(fileHelper.getFileByBusinessId(reviewFileId));
        }

        //构建检查项记录
        CheckItemRecord checkItemRecord = new CheckItemRecord();
        checkItemRecord.setCheckRecordId(checkRecordId);
        List<CheckItemRecord> checkItemRecordList = checkItemRecordService.selectCheckItemRecordList(checkItemRecord);
        checkRecordDetailVO.setCheckItemRecordList(checkItemRecordList);
        return checkRecordDetailVO;
    }

    @Override
    public List<ReportInfoVO> getTodayCheckData(CheckRecordSO checkRecordSO) {
        return checkRecordMapper.getTodayCheckData(checkRecordSO);
    }
}
